//
//  PhotoFilter.m
//  XPhoto
//
//  Created by sentinel on 2020/5/20.
//  Copyright © 2020 baboy. All rights reserved.
//

#import "PhotoFilter.h"

@implementation PhotoFilter
+ (CIFilter *)filterForHotWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CITemperatureAndTint"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:[CIVector vectorWithX:5500 Y:500] forKey:@"inputNeutral"]; // Default value: [6500, 0] Identity: [6500, 0]
    [filter setValue:[CIVector vectorWithX:1500 Y:500] forKey:@"inputTargetNeutral"]; // Default value: [6500, 0] Identity: [6500, 0]
    return filter;
}
+ (CIFilter *)filterForVibranceWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIVibrance"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:@(100) forKey:@"inputAmount"];
    return filter;
}
+ (CIFilter *)filterForZoomBlurWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIZoomBlur"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:[CIVector vectorWithX:originImage.size.width/2 Y:originImage.size.height/2] forKey:@"inputCenter"];
    [filter setValue:@(3) forKey:@"inputAmount"];
    return filter;
}

+ (CIFilter *)filterForCoolWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIPhotoEffectProcess"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    return filter;
}

+ (CIFilter *)filterForFadeWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIPhotoEffectInstant"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    return filter;
}

+ (CIFilter *)filterForGrayWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIPhotoEffectTonal"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    return filter;
}
+ (CIFilter *)filterForVintageWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIPhotoEffectTransfer"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    return filter;
}

+ (CIFilter *)filterForVignetteWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIVignette"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
//    [filter setValue:@(1.0f) forKey:@"inputRadius"];
//    [filter setValue:@(0.0f) forKey:@"inputIntensity"];
    return filter;
}

+ (CIFilter *)filterForSketchWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CILineOverlay"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:@(0.5f) forKey:@"inputNRNoiseLevel"];
    [filter setValue:@(0.71f) forKey:@"inputNRSharpness"];
    [filter setValue:@(0.5f) forKey:@"inputEdgeIntensity"];
    [filter setValue:@(1.1f) forKey:@"inputThreshold"];
    [filter setValue:@(10.0f) forKey:@"inputContrast"];
//    filter = [CIFilter filterWithName:@"CILineOverlay" keysAndValues:kCIInputImageKey, [CIImage imageWithCGImage:originImage.CGImage], nil];
    return filter;
}

+ (CIFilter *)filterForGloomWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CIBloom"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:@(8.f) forKey:@"inputRadius"];
    [filter setValue:@(1.0f) forKey:@"inputIntensity"];
    return filter;
}

+ (CIFilter *)filterForDarkWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CISpotLight"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:[CIVector vectorWithX:-originImage.size.width/3 Y:-originImage.size.height/3 Z:MIN(originImage.size.width, originImage.size.height)/3] forKey:@"inputLightPosition"];
    [filter setValue:[CIVector vectorWithX:originImage.size.width Y:originImage.size.height Z:0] forKey:@"inputLightPointsAt"];
//    [filter setValue:@(3.0f) forKey:@"inputBrightness"];
//    [filter setValue:@(0.1f) forKey:@"inputConcentration"];
//    [filter setValue:[CIColor colorWithRed:0.0f green:0.0f blue:0.0f] forKey:@"inputColor"];
    return filter;
}

+ (CIFilter *)filterForSharpenWithImage:(UIImage *)originImage{
    CIFilter *filter = [CIFilter filterWithName:@"CISharpenLuminance"];
    [filter setValue:[CIImage imageWithCGImage:originImage.CGImage] forKey:kCIInputImageKey];
    [filter setValue:@(0.4) forKey:@"inputSharpness"];
    return filter;
}
+ (UIImage *)image:(UIImage *)originImage withFilter:(NSString *)filterName{
    if (!originImage) {
        return nil;
    }
    CIFilter *filter = [self filter:filterName forImage:originImage];
    if (!filter) {
        return nil;
    }
    
    
//    CIImage *outputImage = [filter outputImage];
    CGImageRef outputImageRef = [[CIContext contextWithOptions:nil] createCGImage:filter.outputImage fromRect:filter.outputImage.extent];
    UIImage *resultImage = [UIImage imageWithCGImage:outputImageRef];
//    UIImage *resultImage = [UIImage imageWithCIImage:outputImage];
    return resultImage;
}
+ (CIFilter *)filter:(NSString *)filterName forImage:(UIImage *_Nullable)originImage{
    if(!filterName){
        return nil;
    }
    NSString *methodName = [NSString stringWithFormat:@"filterFor%@%@WithImage:", [[filterName substringToIndex:1] uppercaseString],[filterName substringFromIndex:1]];
    SEL sel = sel_registerName((const char*)[methodName UTF8String]);
    if (![self respondsToSelector:sel]) {
        return nil;
    }
    IMP imp = [self methodForSelector:sel];
    id (*func)(id, SEL, UIImage *) = (void *)imp;
    CIFilter *filter = func(self, sel, originImage);
    if (!filter) {
        return nil;
    }
    return filter;
}
@end
